package algocity.controlador;

import algocity.modelo.energia.EnergiaInsuficienteException;
import algocity.modelo.juego.ContratableConexion;
import algocity.modelo.juego.DineroInsuficienteException;
import algocity.modelo.juego.JuegoNoIniciadoException;
import algocity.modelo.mapa.FueraDelMapaException;
import algocity.modelo.mapa.Hectarea;
import algocity.modelo.mapa.Operador;
import algocity.modelo.necesidades.SuperficieInvalidaException;
import algocity.vista.MensajeroEstado;
import algocity.vista.SelectorHectarea;
import algocity.modelo.zona.ConstruccionInvalidaExcepcion;

import java.util.Collection;
import java.util.HashSet;

public class ConstruyendoConexion
        implements Construyendo, AvisadorError {

    private final ContratableConexion contratableConstruccion;
    private final Hectarea hectareaOrigen;
    private final MensajeroEstado mensajero;
    private final SelectorHectarea selectorHectarea;
    Collection<Operador<String>> erroresDiferidos;

    public ConstruyendoConexion(ContratableConexion contratableConstruccion, Hectarea hectareaOrigen, MensajeroEstado mensajero, SelectorHectarea selectorHectarea) {
        this.contratableConstruccion = contratableConstruccion;
        this.hectareaOrigen = hectareaOrigen;
        this.mensajero = mensajero;
        this.selectorHectarea = selectorHectarea;
        erroresDiferidos = new HashSet<Operador<String>>();
    }

    @Override
    public void construir() throws FueraDelMapaException, JuegoNoIniciadoException, DineroInsuficienteException, EnergiaInsuficienteException, SuperficieInvalidaException, ConstruccionInvalidaExcepcion {
        mensajero.agregarMensaje("Seleccione la hectárea de destino ...");
        final LlamadorConstructorConexion llamadorConstructorConexion = new LlamadorConstructorConexion(this);

        for ( Operador<String> errorDiferido : erroresDiferidos) {
            llamadorConstructorConexion.registrarError(errorDiferido);
        }

        selectorHectarea.avisarUnaSolaVez(llamadorConstructorConexion);
    }


    public Hectarea getOrigen() {
        return hectareaOrigen;
    }

    public void construir(Hectarea hectareaOrigen, Hectarea hectareaDestino) throws ConstruccionInvalidaExcepcion, SuperficieInvalidaException, JuegoNoIniciadoException, DineroInsuficienteException {
        contratableConstruccion.construir(hectareaOrigen, hectareaDestino);
    }

    @Override
    public void registrarError(Operador<String> observadorError) {
        /*
         Debido a que los errores se producen una vez recibida la segunda hectárea
         estos nos son procesados por esta clase, en caso de producirse, sino por quien
         la recibe, por lo que son almacenados para ser agregados a este al momento de llamarse
         */

        erroresDiferidos.add(observadorError);
    }
}
